﻿Imports Org.BouncyCastle.Pkcs
Imports System.Xml.Serialization
Imports SharedTools
Imports System.ComponentModel
Imports Org.BouncyCastle.Asn1
Imports Org.BouncyCastle.Asn1.Pkcs
Imports Org.BouncyCastle.Asn1.X509

Public Class CertificateRequestItem
    Implements INotifyPropertyChanged

    <XmlIgnore()> Public Property Request As Pkcs10CertificationRequest

    Public Property SerializableRequest As Byte()
        Get
            Return Request.GetDerEncoded
        End Get
        Set(value As Byte())
            Request = New Pkcs10CertificationRequest(value)
        End Set
    End Property

    Public Property UserName As String
    Public Property RequestDateTime As DateTime

    Private _Status As CertificateRequestStatus
    Public Property Status As CertificateRequestStatus
        Get
            Return _Status
        End Get
        Set(value As CertificateRequestStatus)
            _Status = value
            OnPropertyChanged("Status")
        End Set
    End Property

    Public ReadOnly Property RequestType As CertificateType
        Get
            Dim atts = Request.GetCertificationRequestInfo.Attributes
            For Each item In atts
                Dim attr = New Org.BouncyCastle.Asn1.Cms.Attribute(CType(item, Asn1Sequence))

                If attr.AttrType.Equals(PkcsObjectIdentifiers.Pkcs9AtExtendedCertificateAttributes) Then
                    Dim extensions As X509Extensions = X509Extensions.GetInstance(attr.AttrValues(0))

                    For Each e In extensions.ExtensionOids
                        Dim oid As DerObjectIdentifier = DirectCast(e, DerObjectIdentifier)
                        Dim ext As X509Extension = extensions.GetExtension(oid)
                        If oid.Equals(X509Extensions.KeyUsage) Then
                            Dim ku = (New KeyUsage(KeyUsage.DigitalSignature)).GetString
                            If ku = ext.Value.ToString Then
                                Return CertificateType.Signature
                            Else
                                Return CertificateType.Cryptography
                            End If
                        End If
                    Next
                End If
            Next
            Throw New Exception("KeyUsage not set in the request object!")
        End Get
    End Property

    Public Property ID As Integer


#Region "Constructors"
    Public Sub New(req As Pkcs10CertificationRequest, username As String, id As Integer)
        RequestDateTime = DateTime.Now
        Request = req
        Me.UserName = username
        Status = CertificateRequestStatus.Pending
        Me.ID = id
    End Sub

    Public Sub New(reqBytes As Byte(), username As String, id As Integer)
        Me.New(New Pkcs10CertificationRequest(reqBytes), username, id)
    End Sub

    <Obsolete("Only for (de)serialization, should NOT be called directly from code, use one of the overloaded constructors instead")>
    Public Sub New()
        'Empty constructor for de/serialization
    End Sub
#End Region

    Public Event PropertyChanged(sender As Object, e As System.ComponentModel.PropertyChangedEventArgs) Implements System.ComponentModel.INotifyPropertyChanged.PropertyChanged
    Public Overloads Sub OnPropertyChanged(name As String)
        RaiseEvent PropertyChanged(Me, New PropertyChangedEventArgs(name))
    End Sub
End Class
